// Author  : Morbid
// Time    : 2022/08/06 11:12
// FileName: Window.java
// Software: IntelliJ IDEA
package Window;

import com.sun.deploy.security.SelectableSecurityManager;

import javax.swing.*;
import javax.swing.table.DefaultTableCellRenderer;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableColumn;
import java.awt.*;
import java.awt.event.ActionListener;
import java.awt.event.ComponentAdapter;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.Objects;

import static java.lang.StrictMath.pow;

public class Window {

    private JPanel JPanel_main;
    private JTabbedPane JT;
    private JPanel win01;
    private JPanel win02;
    private JPanel JP01;
    private JPanel JP02;
    private JPanel JP03;
    private JPanel JP_first_ip;
    private JPanel JP05;
    private JPanel JP06;
    private JTextField TextField_ip;
    private JButton Button_en;
    private JTextField TextField_mask_nu;
    private JTextField textField_num;
    private JTextField textField_mask;
    private JTextField textField_first_ip;
    private JTextField TextField_last_ip;
    private JTextField textField_gb;
    private JButton Button_cle;
    private JLabel JL_ip;
    private JLabel JL_mask_nu;
    private JLabel JL_num;
    private JLabel JL_mask;
    private JLabel JL_last_ip;
    private JLabel JL_gb;
    private JLabel JL__first_ip;
    private JPanel JP04;
    private JPanel JP7;
    private JLabel JL_network;
    private JTextField textField_network;
    private JPanel JP_21;
    private JPanel JP_22;
    private JTable table;
    private JScrollPane JSP;
    private JPanel JP_01;
    private JTextField textField_AMC;
    private JButton button_en_MAC;
    private JButton button_cle_MAC;
    private JLabel JL_MAC;
    private DefaultTableModel model_table1;

    public Window() {
        //创建窗口
        JFrame frame = new JFrame("地址计算");
        frame.setContentPane(this.JPanel_main);
        frame.setSize(720, 450); //窗体大小
        frame.setLocationRelativeTo(null); //在屏幕上居中显示
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setVisible(true);
        frame.setResizable(false); //不可改变窗口大小

        init();
        listener();
        String[][] a = new String[4][1];
        model_table1 = init_table1(table, a);
    }

    private DefaultTableModel init_table1(JTable table, String[][] data) {
        String[] colnames = {"MAC"};
        DefaultTableModel model = new DefaultTableModel(data, colnames);
        table.setModel(model);
        table.getTableHeader().setReorderingAllowed(false); //表头不可排序
        table.setRowHeight(40);
        table.getTableHeader().setFont(new Font("宋体", Font.BOLD, 20));
        table.setFont(new Font("宋体", Font.PLAIN, 20));
        table.getColumnModel().getColumn(0).setPreferredWidth(15);  //设置列宽
        return model;
    }

    /*!
    初始化方法
     */
    private void init() {
        textField_num.setEditable(false); //不可编辑
        textField_network.setEditable(false);
        textField_mask.setEditable(false);
        textField_first_ip.setEditable(false);
        TextField_last_ip.setEditable(false);
        textField_gb.setEditable(false);
    }

    /*!
    监听按键
     */
    private void listener() {
        Button_en.addActionListener(e -> {
            if (!inspect_ip(TextField_ip.getText())) {
                Information.information_error("ip地址格式错误！");
                TextField_ip.setText("192.168.0.1");
            }
            if (TextField_mask_nu.getText().trim().isEmpty() || (!(Integer.parseInt(TextField_mask_nu.getText()) >= 0 &&
                    Integer.parseInt(TextField_mask_nu.getText()) <= 32))) {
                Information.information_error("掩码位数有误！");
                TextField_mask_nu.setText("24");
            }
            String[] arr = Network();
            textField_num.setText(arr[0]);
            textField_network.setText(arr[1]);
            textField_mask.setText(arr[2]);
            textField_first_ip.setText(arr[3]);
            TextField_last_ip.setText(arr[4]);
            textField_gb.setText(arr[5]);
        });
        Button_cle.addActionListener(e -> {
            clear();
        });
        button_en_MAC.addActionListener(e -> {
            mac();
        });
        button_cle_MAC.addActionListener(e -> {
            clear();
        });
    }

    /*!
    重置
     */
    private void clear() {
        TextField_ip.setText("192.168.0.1");
        TextField_mask_nu.setText("24");
        textField_num.setText("");
        textField_network.setText("");
        textField_mask.setText("");
        textField_first_ip.setText("");
        TextField_last_ip.setText("");
        textField_gb.setText("");
        textField_AMC.setText("");
        for (int i = 0; i < 4; i++) {
            table.setValueAt("", i, 0);
        }
    }

    /*!
    检查IP地址是否合法
     */
    private boolean inspect_ip(String ip) {
        String[] arr = ip.trim().split("\\.");
        if (arr.length != 4)
            return false;
        for (String i : arr) {
            int a = Integer.parseInt(i);
            if (a < 0 || a > 255)
                return false;
        }
        return true;
    }

    public String[] Network() {
        String[] tmp = new String[6];
        String[] ip = TextField_ip.getText().trim().split("\\.");
        String mask_nu = TextField_mask_nu.getText();
        ///可用地址
        tmp[0] = String.valueOf((long) pow(2, 32 - Integer.parseInt(mask_nu)) - 2);
        if (Integer.parseInt(mask_nu) > 30)
            tmp[0] = "这能用？";
        //网络号
        String network_tmp = and(TenToTwo(ip[0], 8) + TenToTwo(ip[1], 8) + TenToTwo(ip[2], 8) +
                TenToTwo(ip[3], 8), mask_numToMask(mask_nu));
        tmp[1] = networkToTen(split_ip(network_tmp));
        //子网掩码
        tmp[2] = networkToTen(split_ip(mask_numToMask(mask_nu)));
        //第一个可用地址
        if (Integer.parseInt(mask_nu) < 31)
            tmp[3] = networkToTen(split_ip(add(network_tmp, 1)));
        else if (Integer.parseInt(mask_nu) == 31)
            tmp[3] = tmp[1];
        else
            tmp[3] = "";
        //最后一个可用地址
        if (Integer.parseInt(mask_nu) < 31)
            tmp[4] = networkToTen(split_ip(add(network_tmp, Integer.parseInt(tmp[0]))));
        else
            tmp[4] = "";
        //广播地址
        if (Integer.parseInt(mask_nu) < 31)
            tmp[5] = networkToTen(split_ip(add(network_tmp, Integer.parseInt(tmp[0]) + 1)));
        else
            tmp[5] = "";
        return tmp;
    }

    public void mac() {
        String MAC_01 = textField_AMC.getText().trim();
        StringBuilder MAC_02 = new StringBuilder();
        String[] MAC = new String[4];
        MAC[0] = MAC[1] = MAC[2] = MAC[3] = "";
        if (MAC_01.length() == 17) {
            char[] arr = MAC_01.toCharArray();
            if ((arr[2] == arr[5] && arr[5] == arr[8] && arr[8] == arr[11] && arr[11] == arr[14])
                    && (arr[2] == '-' || arr[2] == ':'))
                for (char i : arr)
                    if (Character.isLowerCase(i) || Character.isUpperCase(i) || Character.isDigit(i))
                        MAC_02.append(i);
        } else if (MAC_01.length() == 14) {
            char[] arr = MAC_01.toCharArray();
            if ((arr[4] == arr[9]) && (arr[4] == '-' || arr[4] == '.'))
                for (char i : arr)
                    if (Character.isLowerCase(i) || Character.isUpperCase(i) || Character.isDigit(i))
                        MAC_02.append(i);
        } else {
            Information.information_error("MAC地址格式有误！");
            return;
        }
        if (MAC_02.toString().length() != 12)
            Information.information_error("MAC地址格式有误！");
        System.out.println(MAC_02.toString());
        String[] MAC_03 = MAC_02.toString().trim().split("");
        int j = 0;
        for (String i : MAC_03) {
            MAC[0] += i;
            MAC[1] += i;
            MAC[2] += i;
            MAC[3] += i;
            if (j == 1 || j == 3 || j == 5 || j == 7 || j == 9) {
                MAC[0] += "-";
                MAC[1] += ":";
            }
            if (j == 3 || j == 7) {
                MAC[2] += "-";
                MAC[3] += ".";
            }
            j++;
        }
        for (int i = 0; i < 4; i++) {
            table.setValueAt(MAC[i], i, 0);
        }
    }

    public String and(String ip, String mask) {
        String[] mask_tmp = mask.trim().split("");
        StringBuilder tmp = new StringBuilder("");
        int j = 0;
        for (String i : ip.trim().split("")) {
            if (Objects.equals(mask_tmp[j], "1"))
                tmp.append(i);
            else tmp.append("0");
            j++;
        }
        return tmp.toString();
    }

    public String[] split_ip(String network) {
        String newNetwork = network.replaceAll("(.{8})", "$1,");
        return newNetwork.split(",");
    }

    public String networkToTen(String[] networkList) {
        int j = 0;
        StringBuilder tmp = new StringBuilder();
        for (String i : networkList) {
            tmp.append(TwoToTen(i));
            if (j < 3)
                tmp.append(".");
            j++;
        }
        return tmp.toString();
    }

    public String TenToTwo(String Scanner, int n) {
        long num = Integer.parseInt(Scanner);
        StringBuilder base = new StringBuilder();
        long sys = 0;
        while (true) {
            sys = num % 2;
            num = num / 2;
            base.insert(0, sys);
            if (num < 2) {
                sys = num % 2;
                base.insert(0, sys);
                break;
            }
        }
        int len = base.length();
        for (int i = 0; i < n - len; i++) {
            base.insert(0, 0);
        }
        return base.toString();
    }

    public String TwoToTen(String Scanner) {
        return String.valueOf(Integer.parseInt(Scanner, 2));
    }

    public String mask_numToMask(String n) {
        int num = Integer.parseInt(n);
        StringBuilder tmp = new StringBuilder();
        for (int i = 0; i < num; i++) {
            tmp.append("1");
        }
        int len = tmp.length();
        for (int i = 0; i < 32 - len; i++) {
            tmp.append("0");
        }
        return tmp.toString();

    }

    public String add(String num, int n) {
        String[] a = num.trim().split("");
        for (int j = 0; j < n; j++) {
            short x = 1;
            for (int i = a.length - 1; i >= 0; i--) {
                int tmp = Integer.parseInt(a[i]) + x;
                if (tmp == 0) {
                    a[i] = "0";
                    x = 0;
                } else if (tmp == 1) {
                    a[i] = "1";
                    x = 0;
                } else if (tmp == 2) {
                    a[i] = "0";
                    x = 1;
                } else if (tmp == 3) {
                    a[i] = "1";
                    x = 1;
                }
            }
        }
        return arrToString(a, "");
    }

    public String arrToString(String[] arr, String sep) {  //sep为分隔符
        StringBuffer str = new StringBuffer();
        for (int i = 0; i < arr.length; i++) {
            if (i == arr.length - 1) {
                str.append(arr[i]);
            } else {
                str.append(arr[i]);
                str.append(sep);
            }
        }
        return String.valueOf(str);
    }

}
